﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Xml;

namespace Wilke.SharePoint.Tools
{
    public partial class WebConfigModificationsForm : Form
    {
        #region Public Properties

        public List<WebConfigModification> WebConfigModifications { get; set; }
        public XmlDocument XmlDocument { get; set; }

        #endregion

        #region Construction

        public WebConfigModificationsForm()
        {
            InitializeComponent();
        }

        public WebConfigModificationsForm(List<WebConfigModification> webConfigModifications, XmlDocument xmlDocument): this()
        {
            this.WebConfigModifications = webConfigModifications;
            this.XmlDocument = xmlDocument;
        }

        #endregion

        private void WebConfigModificationsForm_Load(object sender, EventArgs e)
        {
            XmlNode xmlNode = null;
            ListViewItem listViewItem = null;
            bool success = false;
            string remark = String.Empty;

            #region Nodes To Remove

            foreach (WebConfigModification webConfigModification in WebConfigModifications)
            {
                try
                {
                    switch (webConfigModification.Type)
                    {
                        case WebConfigModificationType.EnsureAttribute:
                            XmlElement element = XmlDocument.SelectSingleNode(webConfigModification.Path) as XmlElement;
                            if (element != null)
                            {
                                string attributeValue = element.GetAttribute(webConfigModification.Name);
                                if (attributeValue != null)
                                {
                                    success = true;
                                }
                            }
                            else
                            {
                                remark = String.Format("Could not find node '{0}'", webConfigModification.Path);
                            }
                            break;
                        case WebConfigModificationType.EnsureChildNode:
                            XmlNode node = XmlDocument.SelectSingleNode(webConfigModification.Path);
                            if (node != null)
                            {
                                XmlNode oldChild = node.SelectSingleNode(webConfigModification.Name);
                                if (oldChild == null)
                                {
                                    remark = String.Format("Could not find node '{0}{1}{2}'", webConfigModification.Path, webConfigModification.Path.EndsWith("/") ? "" : "/", webConfigModification.Name);
                                }
                                else 
                                {
                                    remark = "Node will be removed.";                                
                                }
                                success = (oldChild != null);
                            }
                            else
                            {
                                remark = String.Format("Could not find node '{0}'", webConfigModification.Path);
                            }
                            break;
                        case WebConfigModificationType.EnsureSection:
                            success = false;
                            remark = "EnsureSection nodes are not removed by SharePoint.";
                            break;
                    }
                }
                catch (Exception exception)
                {
                    remark = exception.Message;
                }

                listViewItem = new ListViewItem();                
                if (webConfigModification.Type == WebConfigModificationType.EnsureAttribute)
                {
                    listViewItem.Text = String.Format("{0}[@{1}='{2}']", webConfigModification.Path, webConfigModification.Name, webConfigModification.Value);
                    listViewItem.Group = listViewWebConfigModifications.Groups["listViewGroupReplace"];
                    if (success)
                    {
                        remark = String.IsNullOrEmpty(webConfigModification.PreviousAttributeValue) ? String.Format("Attribute '{0}' will be removed.", webConfigModification.Name) : String.Format("Attribute '{0}' will contain previous value '{1}'.", webConfigModification.Name, webConfigModification.PreviousAttributeValue );
                    }
                    else
                    {
                        remark = String.Format("Could not locate node '{0}' with attribute '{1}'.", webConfigModification.Path, webConfigModification.Name);
                    }
                    listViewItem.ImageIndex = 0;
                }
                else
                {
                    listViewItem.Text = String.Format("{0}{1}{2}", webConfigModification.Path, webConfigModification.Path.EndsWith("/") ? "" : "/", webConfigModification.Name);
                    listViewItem.Group = listViewWebConfigModifications.Groups["listViewGroupRemove"];
                    if (webConfigModification.Type == WebConfigModificationType.EnsureChildNode)
                    {
                        listViewItem.ImageIndex = 1;
                    }
                    else 
                    {
                        listViewItem.ImageIndex = 2;
                    }
                }
                listViewItem.SubItems.Add((success) ? "1" : "0");
                listViewItem.SubItems.Add(remark);
                listViewWebConfigModifications.Items.Add(listViewItem);
            }

            #endregion

            #region Nodes To Reapply

            foreach (WebConfigModification webConfigModification in WebConfigModifications)
            {
                success = false;
                remark = String.Empty;

                if (webConfigModification.Checked)
                {
                    try
                    {
                        switch (webConfigModification.Type)
                        {
                            case WebConfigModificationType.EnsureAttribute:
                                XmlElement element = XmlDocument.SelectSingleNode(webConfigModification.Path) as XmlElement;
                                if (element == null)
                                {
                                    remark = String.Format("Could not locate node '{0}' with attribute '{1}'.", webConfigModification.Path, webConfigModification.Name);
                                }
                                else
                                {
                                    string attributeValue = element.GetAttribute(webConfigModification.Name);
                                    if (attributeValue != null)
                                    {
                                        remark = "Attribute will be updated." ;
                                    }
                                    else
                                    {
                                        remark = "Attribute will be added." ;
                                    }
                                }
                                success = (element != null);
                                break;
                            case WebConfigModificationType.EnsureChildNode:
                                xmlNode = XmlDocument.SelectSingleNode(webConfigModification.Path);
                                if (xmlNode != null)
                                {
                                    XmlNode oldChild = xmlNode.SelectSingleNode(webConfigModification.Name);
                                    if (oldChild == null)
                                    {
                                        remark = String.Format("Could not find node '{0}{1}{2}'", webConfigModification.Path, webConfigModification.Path.EndsWith("/") ? "" : "/", webConfigModification.Name);
                                    }
                                    else 
                                    {
                                        remark = "Node will be added.";                                    
                                    }
                                    success = (oldChild != null);
                                }
                                else
                                {
                                    remark = String.Format("Could not find node '{0}'", webConfigModification.Path);
                                }
                                break;
                            case WebConfigModificationType.EnsureSection:
                                xmlNode = XmlDocument.SelectSingleNode(webConfigModification.Path);
                                if (xmlNode != null)
                                {
                                    XmlNode oldChild = xmlNode.SelectSingleNode(webConfigModification.Name);
                                    if (oldChild == null)
                                    {
                                        remark = String.Format("Could not find section '{0}{1}{2}'", webConfigModification.Path, webConfigModification.Path.EndsWith("/") ? "" : "/", webConfigModification.Name);
                                    }
                                    else 
                                    {
                                        remark = "Section will be added.";          
                                    }
                                    success = (oldChild != null);
                                }
                                else
                                {
                                    remark = String.Format("Could not find section '{0}'", webConfigModification.Path);
                                }
                                break;
                        }
                    }
                    catch (Exception exception)
                    {
                        remark = exception.Message;
                    }

                    listViewItem = new ListViewItem();
                    if (webConfigModification.Type == WebConfigModificationType.EnsureAttribute)
                    {
                        listViewItem.Text = String.Format("{0}[@{1}='{2}']", webConfigModification.Path, webConfigModification.Name, webConfigModification.Value);
                        listViewItem.Group = listViewWebConfigModifications.Groups["listViewGroupReplace"];                       
                        listViewItem.ImageIndex = 0;
                    }
                    else
                    {
                        listViewItem.Text = String.Format("{0}{1}{2}", webConfigModification.Path, webConfigModification.Path.EndsWith("/") ? "" : "/", webConfigModification.Name);
                    }
                    listViewItem.Group = listViewWebConfigModifications.Groups["listViewGroupAdd"];
                    
                    listViewItem.SubItems.Add((success) ? "1" : "0");
                    listViewItem.SubItems.Add(remark);
                    switch (webConfigModification.Type)
                    { 
                        case WebConfigModificationType.EnsureAttribute:
                            listViewItem.ImageIndex = 0;
                            break;
                        case WebConfigModificationType.EnsureChildNode:
                            listViewItem.ImageIndex = 1;
                            break;
                        case WebConfigModificationType.EnsureSection:
                            listViewItem.ImageIndex = 2;
                            break;
                    }
                    listViewWebConfigModifications.Items.Add(listViewItem);

                }
            }

            #endregion
        }

        private void listViewWebConfigModifications_DrawColumnHeader(object sender, DrawListViewColumnHeaderEventArgs e)
        {
            e.DrawDefault = true;
        }

        private void listViewWebConfigModifications_DrawItem(object sender, DrawListViewItemEventArgs e)
        {
            e.DrawBackground();
            e.DrawText();
        }

        private void listViewWebConfigModifications_DrawSubItem(object sender, DrawListViewSubItemEventArgs e)
        {   
            Rectangle bounds = new Rectangle(e.Bounds.Location, e.Bounds.Size);

            if (e.ColumnIndex == 1)
            {
                e.Graphics.DrawImage((e.Item.SubItems[1].Text == "1") ? Properties.Resources.OK : Properties.Resources.NOK, bounds.X + (bounds.Width / 2) - 8, bounds.Y);
            }
            else 
            {
                e.DrawDefault = true;
            }
        }

        private void WebConfigModificationsForm_KeyDown(object sender, KeyEventArgs e)
        {
            if (e.KeyCode == Keys.Escape)
            {
                this.Close();
            }
        }
    }
}
